﻿using System;

namespace crc_1
{
    public class Class1
    {
        public ushort crc16_modbus(ushort[] data, uint data_len)
        {
            ushort CRCin = 0xffff;
            ushort CRCret = 0;

            for (int i = 0; i < data_len; i++)
            {
                CRCin = (ushort)(data[i] ^ CRCin);
                for (int j = 0; j < 8; j++)
                {
                    if ((CRCin & 0x01) == 1)
                    {
                        CRCin = (ushort)(CRCin >> 1);
                        CRCin = (ushort)(CRCin ^ 0xa001);
                    }
                    else
                    {
                        CRCin = (ushort)(CRCin >> 1);
                    }
                }
            }

            CRCret = (ushort)(CRCin >> 8);
            CRCret = (ushort)(CRCret | (CRCin << 8));

            return CRCret;
        }
        // 计算输入字符串的CRC-16/XMODEM值并返回16进制字符串
        public static string CalculateCrc16Xmodem(string input)
        {
            if (string.IsNullOrEmpty(input))
                throw new ArgumentNullException(nameof(input), "输入字符串不能为空");

            // 将字符串转换为字节数组（使用UTF-8编码）
            byte[] data = System.Text.Encoding.UTF8.GetBytes(input);

            // 计算CRC-16/XMODEM
            ushort crc = ComputeCrc16Xmodem(data);

            // 转换为16进制字符串（大写，固定4位，不足补零）
            return crc.ToString("X4");
        }

        // CRC-16/XMODEM核心计算方法
        private static ushort ComputeCrc16Xmodem(byte[] data)
        {
            ushort crc = 0x0000;  // 初始值为0
            const ushort polynomial = 0x1021;  // 多项式0x1021

            foreach (byte b in data)
            {
                crc ^= (ushort)(b << 8);  // 将当前字节与CRC高8位异或

                for (int i = 0; i < 8; i++)
                {
                    if ((crc & 0x8000) != 0)  // 如果最高位为1
                        crc = (ushort)((crc << 1) ^ polynomial);  // 左移并异或多项式
                    else
                        crc <<= 1;  // 仅左移
                }
            }

            return crc;  // 返回计算结果
        }
    }
}
